﻿/**************************************************************
 *
 * 唯一标识：99b060da-1e92-40c8-a149-eda1679394bf
 * 命名空间：Sgr.UPMS.Controllers
 * 创建时间：2023/8/25 15:43:42
 * 机器名称：DESKTOP-S0D075D
 * 创建者：antho
 * 电子邮箱：fengqinhua2016@163.com
 * 描述：
 *
 **************************************************************/

using MediatR;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Sgr.Application.Queries;
using Sgr.Application.ViewModels;
using Sgr.AspNetCore.ActionFilters.AuditLogs;
using Sgr.AspNetCore.ActionFilters.Permissions;
using Sgr.UPMS.Application.Commands.Organizations;
using Sgr.UPMS.Application.Queries;
using Sgr.UPMS.Application.ViewModels;

namespace Sgr.UPMS.Controllers
{
    /// <summary>
    /// 组织机构管理接口
    /// </summary>
    [Route("api/v1/sgr/organizations")]
    [ApiController]
    [Produces("application/json")]
    [Tags("Organization")]
    public class OrganizationController : ControllerBase
    {
        private readonly IMediator _mediator;
        private readonly IOrganizationQueries _organizationQueries;

        /// <summary>
        /// 初始化组织机构管理控制器
        /// </summary>
        public OrganizationController(IMediator mediator,
            IOrganizationQueries organizationQueries)
        {
            _mediator = mediator ?? throw new ArgumentNullException(nameof(mediator));
            _organizationQueries = organizationQueries ?? throw new ArgumentNullException(nameof(organizationQueries));
        }

        #region Commond

        /// <summary>
        /// 创建组织机构
        /// </summary>
        /// <param name="command">创建组织机构的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <remarks>
        /// 示例请求:
        ///
        ///     POST /api/v1/sgr/organizations
        ///     {
        ///         "name": "示例公司",
        ///         "staffSizeCode": "SIZE_100",
        ///         "orgTypeCode": "ENTERPRISE",
        ///         "areaCode": "100000",
        ///         "leader": "张三",
        ///         "phone": "13800138000",
        ///         "email": "example@company.com",
        ///         "adminName": "admin",
        ///         "adminPassword": "password123"
        ///     }
        /// </remarks>
        /// <response code="200">创建成功</response>
        /// <response code="400">请求参数验证失败</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.CreateOrg)]
        [HttpPost]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("创建组织机构")]
        public async Task<ActionResult<bool>> CreateAsync([FromBody] CreateOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        /// <summary>
        /// 更新组织机构信息
        /// </summary>
        /// <param name="command">更新组织机构的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">更新成功</response>
        /// <response code="400">请求参数验证失败</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.UpdateOrg, Permissions.AssociatedParentOrg)]
        [HttpPut]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("更新组织机构")]
        public async Task<ActionResult<bool>> UpdateAsync([FromBody] UpdateOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        /// <summary>
        /// 注销组织机构
        /// </summary>
        /// <param name="command">注销组织机构的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">注销成功</response>
        /// <response code="400">请求参数验证失败</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.CancellationOrg)]
        [HttpPost("cancellation")]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("注销组织机构")]
        public async Task<ActionResult<bool>> CancellationAsync([FromBody] CancellationOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        /// <summary>
        /// 恢复组织机构
        /// </summary>
        /// <param name="command">恢复组织机构的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">恢复成功</response>
        /// <response code="400">请求参数验证失败</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.RecoverOrg)]
        [HttpPost("recover")]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("恢复组织机构")]
        public async Task<ActionResult<bool>> RecoverAsync([FromBody] RecoverOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        /// <summary>
        /// 注册新组织机构
        /// </summary>
        /// <param name="command">注册组织机构的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">注册成功</response>
        /// <response code="400">请求参数验证失败</response>
        [HttpPost("register")]
        [AllowAnonymous]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("注册组织机构")]
        public async Task<ActionResult<bool>> RegisterAsync([FromBody] RegisterOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        /// <summary>
        /// 关联上级组织机构
        /// </summary>
        /// <param name="command">关联上级组织的请求参数</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">关联成功</response>
        /// <response code="400">请求参数验证失败</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.AssociatedParentOrg)]
        [HttpPost("parent-association")]
        [ProducesResponseType(typeof(bool), StatusCodes.Status200OK)]
        [AuditLogActionFilter("关联上级组织")]
        public async Task<ActionResult<bool>> AssociateParentAsync([FromBody] AssociatedParentOrgCommand command, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _mediator.Send(command, cancellationToken);
            return !result.IsSuccess ? this.CustomBadRequest(result.Message) : Ok(result.Data);
        }

        #endregion Commond

        #region Queries

        /// <summary>
        /// 获取当前登录用户所属组织的基本信息
        /// </summary>
        /// <param name="currentUser">当前用户</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">获取成功</response>
        /// <response code="401">未经授权的访问</response>
        /// <response code="404">组织不存在</response>
        [CheckPermission(Permissions.ViewCurrentOrg)]
        [HttpGet("current/basic")]
        [ProducesResponseType(typeof(OutOrganizationViewModel), StatusCodes.Status200OK)]
        [ProducesResponseType(StatusCodes.Status404NotFound)]
        [AuditLogActionFilter("获取当前用户所属组织基本信息")]
        public async Task<ActionResult<OutOrganizationViewModel>> GetCurrentOrgBasicInfoAsync(
            [FromServices] ICurrentUser currentUser, System.Threading.CancellationToken cancellationToken)
        {
            long orgId = QueryHelper.GetOrgId(currentUser);
            var result = await _organizationQueries.GetByIdAsync(orgId, cancellationToken);
            return result == null ? NotFound() : Ok(result);
        }

        /// <summary>
        /// 获取组织机构详情
        /// </summary>
        /// <param name="id">组织机构ID</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">获取成功</response>
        /// <response code="401">未经授权的访问</response>
        /// <response code="404">指定的组织机构不存在</response>
        [CheckPermission(Permissions.ViewOrg)]
        [HttpGet("{id:long:min(1)}")]
        [ProducesResponseType(typeof(OutOrganizationViewModel), StatusCodes.Status200OK)]
        [ProducesResponseType(StatusCodes.Status404NotFound)]
        [AuditLogActionFilter("获取组织机构详情")]
        public async Task<ActionResult<OutOrganizationViewModel>> GetByIdAsync([FromRoute] long id, System.Threading.CancellationToken cancellationToken)
        {
            var result = await _organizationQueries.GetByIdAsync(id, cancellationToken);
            return result == null ? NotFound() : Ok(result);
        }

        /// <summary>
        /// 查询组织机构列表
        /// </summary>
        /// <param name="request">查询条件</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <remarks>
        /// 示例请求:
        ///
        ///     POST /api/v1/sgr/organizations/search
        ///     {
        ///         "code": "ORG001",
        ///         "orgTypeCode": "ENTERPRISE",
        ///         "parentId": 1,
        ///         "pageIndex": 1,
        ///         "pageSize": 10
        ///     }
        /// </remarks>
        /// <response code="200">查询成功</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.ViewOrg)]
        [HttpPost("search")]
        [ProducesResponseType(typeof(PagedResponse<OutOrganizationPagedModel>), StatusCodes.Status200OK)]
        [AuditLogActionFilter("查询组织机构列表")]
        public async Task<ActionResult<PagedResponse<OutOrganizationPagedModel>>> SearchAsync(
            [FromBody] InOrganizationSearchModel request, System.Threading.CancellationToken cancellationToken)
        {
            return Ok(await _organizationQueries.GetPagedListAsync(request, cancellationToken));
        }

        /// <summary>
        /// 根据名称或识别码快速查询组织机构（简要信息）
        /// </summary>
        /// <param name="searchText">查询关键字（组织机构名称或识别码）</param>
        /// <param name="limit">返回记录数量限制（默认10条，最大100条）</param>
        /// <param name="onlyActive">是否仅返回正常状态的记录（默认true）</param>
        /// <param name="cancellationToken">取消令牌</param>
        /// <response code="200">查询成功</response>
        /// <response code="401">未经授权的访问</response>
        [CheckPermission(Permissions.ViewOrg)]
        [HttpGet("lookup")]
        [ProducesResponseType(typeof(IEnumerable<NameValue>), StatusCodes.Status200OK)]
        [AuditLogActionFilter("组织机构快速查询")]
        public async Task<ActionResult<IEnumerable<NameValue>>> GetOrganizationLookupAsync(
            [FromQuery] string searchText,
            [FromQuery] int limit = 10,
            [FromQuery] bool onlyActive = true,
            System.Threading.CancellationToken cancellationToken = default)
        {
            // 限制最大返回数量，防止滥用
            var actualLimit = Math.Min(Math.Max(limit, 1), 20);

            var result = await _organizationQueries.GetOrganizationLookupAsync(
                searchText,
                actualLimit,
                onlyActive,
                cancellationToken);

            return Ok(result);
        }

        #endregion Queries
    }
}